/***********************************************************************************
 * 文件名： TDevCom.h
 * 作者： 刘言
 * 版本： 2
 * 说明：
 * 		与要读写的目标设备的通信协议实现，合并了雾化器设备、电池设备、一体雾化套装设备。
 * 	    通信协议更多细节参考《雾化器通信协议》、《读写器与电池通信协议》、《读写器与一体雾化套
 *  装通信协议》文档。
 *      本文件使用面向对象的思想设计，C++的Class将属性（变量）和函数封装在一起，C语言使用
 *  struct可以一定程度上替代Class。虽然struct也可以利用函数指针变量的方式将函数封装在struct内
 *  部，但是实例化对象时总需要重复的给这些函数指针赋值，会增加一些代码量，而且函数指针本身也会
 *  增加RAM使用量。
 *      本文件面向对象的实现方案是：在struct内只封装属性，通过调用统一的函数来操作不同的对象。
 *  损失了一定的封装性，但是节省了一定的资源，规避了 KEIL C51 编译器可能的函数指针功能不完善引
 *  起的问题。
 *      使用之前需要先实例化（定义）一个TDevCom对象,然后对其进行初始化（设置基础属性）。调用函
 *  数来操作对象时必须将对象地址传递给函数（第一个参数）。
 * 		本文件提供了以下接口函数：
 *      TDevCom_Init: 初始化 TDevCom 对象
 *      TDevCom_GetErrorCode: 获取错误码
 *      TDevCom_SetEncrypt: 设置是否加密通信
 * 		TDevCom_Enter: 进入通信状态，注意一般会影响中断响应
 * 		TDevCom_Exit: 退出通信状态
 * 		TDevCom_Write:  向目标设备的存储器写入数据
 * 		TDevCom_Read: 从目标设备的存储器读出数据
 * 		使用流程: 初始化后，先调用 TDevCom_Enter 与目标设备建立通信同步，然后调用 TDevCom_Write 或者 
 * 		TDevCom_Read 等进行操作，最后 TDevCom_Exit。
 * 修改记录：
 * 	2020/6/8: 初版。 刘言。
 *  2020/6/19: 2 增加 TDevCom_SetEncrypt 。刘言。
***********************************************************************************/
#ifndef _TDEVCOM_H_
#define _TDEVCOM_H_

#include "ptc.h"
#include "thread_com.h"

// 自定义类型

// 协议类型
typedef enum _protocol
{
    TDEVCOM_ATOMIZER,
    TDEVCOM_BATTERY_INTEGRATED
}protocol_t;

// 错误码
typedef enum _TDevCom_error_code
{
    // 前面的值参考 ptc_errcode_t tc_errcode_t

    TDEVCOM_AUTH_CODE_ERR = 0xA0,	//收到的认证码错误
    TDEVCOM_UNKNOW_CMD,
    TDEVCOM_NO_PERMISSION
}TDevCom_error_code_t;

// 命令表结构体
typedef struct _cmd_list
{
    u8 WRITE;
    u8 READ;
    u8 DATA;
    u8 RETURN;
}cmd_list_t;

#define TDEVCOM_BATT_INTE_CMD_LIST   \
{                               \
    0x10,                       \
    0x11,                       \
    0xFC,                       \
    0xFE                        \
}

#define TDEVCOM_ATOM_CMD_LIST   \
{                               \
    0x14,                       \
    0x12,                       \
    0xFC,                       \
    0xFE                        \
}

// TDevCom 类 [目标设备通信(协议)]
typedef struct _TDevCom
{
    // 基础属性

    protocol_t mProtocol;   // 参照哪个协议文档进行通信（目前对应设备类型）
    TDevCom_error_code_t mErrorCode;// 错误码
    u8 mLimitCode;          // 通信限制码
    const cmd_list_t code *pCmdList;   // 命令表
    bool mEncrypt;          // 是否加密
    bool mWriteTime;        // 是否写时间（WRITE命令是否附加时间参数）

    // 以下是加密通信需要的参数

    u8 mBackCode;           // 回应码，由来自从机的随机数计算得来，主机与从机都必须保存，如果一方发现回应码错误说明对方是仿品，将拒绝回应
    u8 mPassCode;           // 密码，主机随机生成，数据区的数据都是利用这个密码加密的
    u8 mAuthCode;           // 认证码，从机解密上一包主机发来的数据后，使用解密后的数据计算得来，主机将以此来验证从机的身份

}TDevCom;



// 对外接口

void TDevCom_Init(TDevCom *obj, protocol_t protocol, u8 limit_code);
bool TDevCom_Enter(TDevCom *obj);
void TDevCom_Exit(TDevCom *obj);
bool TDevCom_Write(TDevCom *obj, u16 addr,const u8 * buff,u8 length);
bool TDevCom_Read(TDevCom *obj, u16 addr,u8 * buff,u8 length);
TDevCom_error_code_t TDevCom_GetErrorCode(TDevCom *obj);
void TDevCom_SetEncrypt(TDevCom *obj ,bool val, const u8 *rand);

#endif
